--EPG-Flex老化脚本
import("System")
import("System.IO.Ports")
import("Jodell.Studio.Lua","Jodell.Studio.Lua")

local master = Lua_EcMaster()
local adapters = master:FindAdapters()  -- 获取所有网络适配器 
-- 遍历适配器并打印信息
for i=0,adapters.Count-1 do
    print(string.format("Name: %s\t\t\tDescription: %s", adapters[i].Name, adapters[i].Description))
end
master:Start("\\Device\\NPF_{A1D14E0D-7382-4F14-B044-FB67A066F18D}") -- 启动适配器, 需根据实际适配器名称填写
-- 获取从站
for i=0,master.Slaves.Count-1 do
    print(master.Slaves[i].Name .. "    " .. master.Slaves[i].ProductCode)
end

--*******************************数据存储地址*******************************--
local path1 = "d:\\EPG-flex老化测试记录.csv"
writer = Lua_CsvWriter(path1)
writer:Open()

--*********************************参数定义*********************************--
local parameter = {
    closePos = 0, -- 闭合位置
    closeSpeed = 60000, -- 闭合速度
    closeForce = 2000, -- 闭合力
    openPos = 2600, -- 打开位置
    openSpeed = 60000,-- 打开速度
    openForce = 2000,-- 打开力
    DecelerationSectionPosition = 80, -- 减速段位置
    DecelerationSpeed = 5, -- 减速段速度
    DecelerationDirection = 1, -- 减速段方向

}
--*****************************参数主索引/子索引*****************************--
local primaryIndex = 0x7000
local subindexes = {
    closePos = 0x08, -- 闭合位置
    closeSpeed = 0x09, -- 闭合速度
    closeForce = 0x0A, -- 闭合力
    openPos = 0x0B, -- 打开位置
    openSpeed = 0x0C, -- 打开速度
    openForce = 0x0D,-- 打开力
    DecelerationSectionPosition = 0x16, -- 减速段位置
    DecelerationSpeed = 0x17, -- 减速段速度
    DecelerationDirection = 0x18 -- 减速段方向
}
--*********************************参数写入*********************************--
function writeParameters()
    for id = 0,1 do
        for key, value in pairs(parameter) do
            local subindex = subindexes[key] 
            if subindex then 
                local ret = master:WritePdo_UInt16(id, primaryIndex, subindex, value) -- 发送参数值到设备
                if ret == 0 then
                    Info(string.format("%d号设备参数写入成功,写入值:%d",id,value))
                else
                    Info(string.format("%d号设备参数写入失败",id))
                end
            else
                Info("警告：未找到" .. key .. "的子索引")
            end
        end
    end
end

--*********************************设备使能*********************************--
function Enable()
    local startTime = 0
    local readTime = 0
    for id = 0,1 do
        -- 发送启用命令给设备
        ret = master:WritePdo_UInt16(id, 0x7000, 0x04, 0x01)
        -- 检查命令是否发送成功
        if ret == 0 then
            -- 等待设备处理命令
            Delay(80)
            -- 持续检查设备状态直到设备启用成功或超时
            while true do
                -- 记录开始时间
                startTime = os.clock()
                -- 从设备读取状态
                ret,state = master:ReadPdo_UInt16(id, 0x6000, 0x01)
                -- 检查设备是否已启用
                if ret == 0 then
                    if state == 4 then
                        Info(string.format("%d号设备使成功,读取状态成功，状态值:%d,", id, state))
                        break
                    end
                end
                -- 计算从上一次读取操作开始到现在的时间间隔
                local currentTime = os.clock()
                readTime = currentTime - startTime
                -- 检查是否超时
                if readTime > 10 then
                    Info(string.format("%d号设备使能失败,读取状态超时，状态值:%d,", id, state))
                    break
                end
                Delay(100)
            end
        else
            Info(string.format("%d号设备发送启用命令失败", id))
        end
    end
end

--*********************************设备动作*********************************--
function openorclose(value)
    local ret1 = {}
    local actions = {
        {id = 0, action = value},
        {id = 1, action = value}
    }
    for _, action in ipairs(actions) do
        local id = action.id
        local ret = master:WritePdo_UInt16(id, 0x7000, 0x06, action.action)
    end
    Delay(80)
    for _, action in ipairs(actions) do
        local id = action.id
        -- local ret = master:WritePdo_UInt16(id, 0x7000, 0x06, action.action)
        if ret == 0 then
            while 1 do
                -- 记录开始时间
                startTime = os.clock()
                -- 从设备读取状态
                ret,state = master:ReadPdo_UInt16(id, 0x6000, 0x02)
                -- 检查设备是否已启用
                if ret == 0 then
                    if state == 9 or state == 10  then
                        if value == 1 then
                            ret1[#ret1+1]=(string.format("%d,%d,", id,state))
                            break
                        elseif value == 0 then
                            ret1[#ret1+1] = (string.format("%d,%d,", id,state))
                            break
                        end
                    end
                end
                -- 计算从上一次读取操作开始到现在的时间间隔
                local currentTime = os.clock()
                readTime = currentTime - startTime
                -- 检查是否超时
                if readTime > 3 then
                    Info(string.format("%d号设备动作失败,读取状态超时，状态值:%d,",id, state))
                    break
                end
                Delay(100)
            end
        else
            Info(string.format("%d号设备发送启用命令失败", id))
        end
    end
    return ret1
end

local i = 0
writer:WriteString(string.format("测试次数(次),样品编号,打开状态,样品编号,打开状态,,样品编号,闭合状态,样品编号,闭合状态\n"))
writeParameters()
Delay(1000)
Enable()
Delay(2000)

while true do
    i = i + 1
    local abb = openorclose(1) -- 打开
    Delay(1000)
    local acc = openorclose(0) -- 关闭
    Delay(1000)
    local str = string.format("%d,%s,%s\n", i,table.concat(abb),table.concat(acc))
    writer:WriteString(str)
    Info(str)
end

master:Stop()